﻿//========================================
// All rights reserved (C) 2017-2100
// CLR 版本：	4.0.30319.42000
// 命名空间:	SFJDService.TransportHandle
// 文 件 名：	ReceivePacket
// 作    者：	WooG
// 联系方式：	wooglle@163.com
// 创建时间：	2018/6/18 14:27:03
//========================================
using Common;
using System.Collections.Generic;
using System.Threading;

namespace SFJDService.TransportHandle
{
    public class ReceivePacket
    {
        const int BlockMaxCount = 20;
        static List<ReceiveBlock> blockList = new List<ReceiveBlock>(BlockMaxCount);
        static int BlockCount = 0;
        PacketFileCheck[] finelist = new PacketFileCheck[BlockMaxCount * ReceiveBlock.MaxCount * 10];
        int fineIndex = 0;

        public ReceivePacket(ClassTransportInfo transportInfo, byte[] sockBytes)
        {
            PacketFileTransport packet = new PacketFileTransport(sockBytes);
            PacketFileCheck check = new PacketFileCheck(packet.Check(), packet.FileIndex, packet.ByteIndex);
            if (check.Boolean)
            {
                TransportReceive.instance.SendBackCheck(check); //向发送端返回验证消息
            }
            
            for(int i = 0; i < finelist.Length; i++)
            {
                if(finelist[i] == check) //重复的发包，包已经处理过
                {
                    return;
                }
            }
            fineIndex++;
            fineIndex = fineIndex + 1 > finelist.Length ? 0 : fineIndex;
            finelist[fineIndex] = check; //存入校验过的数据包的列表， 循环存入

            //while (BlockCount > BlockMaxCount) { } //线程等待， 防止block过多内存溢出
            lock (blockList)
            {
                bool hasHandle = false;
                for(int i = blockList.Count - 1; i >= 0; i--)
                {
                    switch (blockList[i].AddPacket(transportInfo, packet))
                    {
                        case -1: //不属于此块
                            break;
                        case 0: //已经加入此块
                            hasHandle = true;
                            break;
                        case 1: //已经加入此块，且此块已满
                            blockList.RemoveAt(i);
                            BlockCount--;
                            hasHandle = true;
                            break;
                    }
                    if (hasHandle)
                    {
                        break;
                    }
                }
                if (!hasHandle)//加入一个新的块
                {
                    blockList.Add(new ReceiveBlock(transportInfo, packet));
                    BlockCount++;
                }
            }
        }
    }
}
